﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using DatabaseAccess.DBUtility;
using System.Data;
//Description:排产定时任务通用处理类
//Copyright (c) : 通力凯顿（北京）系统集成有限公司
//Writer:zhangrj
//create Date:2023-10-31
//Rewriter:
//Rewrite Date:

namespace MESScheduledTask
{
    public class CommonHelper
    {
        /// <summary>
        /// 获取定时任务的属性 add by zhangrj 20231031
        /// </summary>
        /// <param name="scheduledTaskID"></param>
        /// <returns></returns>
        public static Dictionary<string, string> GetTaskAttr(string scheduledTaskID)
        {
            Dictionary<string, string> dic = new Dictionary<string, string>();
            string sql = string.Format(@"SELECT sr.attributename,sr.attributevalue FROM SCHEDULEDTASKATTR sr WHERE sr.scheduledtaskid = '{0}'", scheduledTaskID);
            DataTable dt = DatabaseHelper.Query_ReturnDatTable(sql);
            foreach (DataRow item in dt.Rows)
            {
                dic.Add(item["attributename"].ToString(), item["attributevalue"].ToString());
            }
            return dic;
        }

        /// <summary>
        /// 写入任务日志
        /// </summary>
        /// <param name="id"></param> 
        /// <param name="status">2：执行中 3：错误 4:已完成</param> 
        /// <param name="executeType">执行类型：1：自动，2：手动</param> 
        public static void WriteTaskLog(string id, string status, string msg, string executeType)
        {
            var strSql = @"--记录日志
declare
id VARCHAR2(60);
v_count number;
v_status varchar2(5);
v_starttime date;
begin
    v_status:='{1}';
    select count(sl.scheduledtasklogsid) into v_count from ScheduledTaskLogs sl 
    where sl.scheduledtaskid='{0}' and sl.islatest=1 and sl.taskexeendtime is null;    
    
    if v_count=0 then  
      v_starttime:=sysdate;
      update ScheduledTaskLogs set Islatest=0 where  ScheduledTaskid='{0}' and Islatest=1;  
     
      insert into ScheduledTaskLogs sl (sl.scheduledtasklogsid,sl.scheduledtaskid,sl.status,sl.islatest,sl.ManualOperEmp,sl.executetype,
sl.createdate,sl.taskexestarttime,sl.taskexeendtime,sl.logmessage) values (sys_guid(),'{0}','{1}',1,'','{3}',sysdate,sysdate,null,'{2}');     
    else
      select sl.scheduledtasklogsid,sl.taskexestarttime into id,v_starttime from ScheduledTaskLogs sl 
      where sl.scheduledtaskid='{0}' and sl.islatest=1 and sl.taskexeendtime is null and rownum=1;
      
      update ScheduledTaskLogs sl set sl.taskexeendtime=sysdate,sl.status='{1}',sl.logmessage=sl.logmessage||'{2}' where 
      scheduledtasklogsid=id;
    end if;
    
    if v_status='4' then
      v_status:='1';
    end if;
    
    update ScheduledTask set Status=v_status,Nextexcutime=v_starttime+CycleTime where ScheduledTaskid='{0}';
    commit;
end;";
            DatabaseHelper.ExecuteSql(string.Format(strSql, id, status, msg, executeType));
        }

        /// <summary>
        /// 记录批次定时日志
        /// </summary>
        public static void WriteContainerLog(string id, string containerid, string containername, string msg, int taskType)
        {
            string strSql = @"begin
                  update ContainerScheduledTaskLogs cl set cl.islatest=0 where scheduledtaskid='{0}' and cl.containerid='{1}' and Islatest=1;
                  insert into ContainerScheduledTaskLogs cl (ContainerScheduledTaskLogsID,scheduledtaskid,ContainerID,Containername,
                  IsLatest,LogMessage,CreateDate,TaskType) values (sys_guid(),'{0}','{1}','{2}',1,'{3}',sysdate,{4});
                  commit;
                end;";
            DatabaseHelper.ExecuteSql(string.Format(strSql, id, containerid, containername, msg, taskType));
        }
        /// <summary>
        /// 更新定时任务日志的开始时间 add by zhangrj 20240328
        /// </summary>
        /// <param name="scheduledtaskID">任务ID</param>
        public static void UpdateTaskLogStartDate(string scheduledtaskID)
        {
            string strSql = string.Format(@"UPDATE ScheduledTaskLogs s SET s.taskexestarttime = sysdate WHERE s.scheduledtaskid = '{0}' AND s.islatest = 1 AND s.taskexeendtime is null", scheduledtaskID);
            DatabaseHelper.ExecuteSql(strSql);
        }

        /// <summary>
        /// 获取需要执行的任务
        /// </summary>
        /// <returns></returns>
        public static DataTable GetNeedExecuteTask(TaskTypeEnum taskType)
        {
            string strSql = @"select '手动执行中' TYPE,st.scheduledtaskid,st.taskname,st.taskdesc,st.factoryid,f.factoryname,st.taskstarttime,st.taskendtime,sl.taskexestarttime,st.cycletime,DECODE(SL.TASKEXESTARTTIME,NULL,TO_CHAR(ST.TASKSTARTTIME+ST.CYCLETIME,'YYYY-MM-DD HH24:MI:SS'),TO_CHAR(SL.TASKEXESTARTTIME+ST.CYCLETIME,'YYYY-MM-DD HH24:MI:SS'))
                            NEXTEXCUTIME2,st.NEXTEXCUTIME from ScheduledTask st 
                            LEFT JOIN factory f ON f.factoryid = st.factoryid
                            left join ScheduledTaskLogs sl on st.ScheduledTaskid=sl.ScheduledTaskid and sl.islatest=1
                            WHERE st.tasktype = {0} and st.isuse=0 and st.status!=3 and sl.executetype=2 and sl.taskexeendtime is null
                            union all
                            select '自动执行中' TYPE,st.scheduledtaskid,st.taskname,st.taskdesc,st.factoryid,f.factoryname,st.taskstarttime,st.taskendtime,sl.taskexestarttime,st.cycletime,DECODE(SL.TASKEXESTARTTIME,NULL,TO_CHAR(ST.TASKSTARTTIME+ST.CYCLETIME,'YYYY-MM-DD HH24:MI:SS'),TO_CHAR(SL.TASKEXESTARTTIME+ST.CYCLETIME,'YYYY-MM-DD HH24:MI:SS'))
                            NEXTEXCUTIME2,st.NEXTEXCUTIME from ScheduledTask st 
                            LEFT JOIN factory f ON f.factoryid = st.factoryid
                            left join ScheduledTaskLogs sl on st.ScheduledTaskid=sl.ScheduledTaskid and sl.islatest=1
                            WHERE st.tasktype = {0} and st.isuse=0 and st.status!=3 and sl.executetype=1 and sl.taskexeendtime is null
                            union all
                            select '自动未执行' TYPE,st.scheduledtaskid,st.taskname,st.taskdesc,st.factoryid,f.factoryname,st.taskstarttime,st.taskendtime,null taskexestarttime,st.cycletime,DECODE(SL.TASKEXESTARTTIME,NULL,TO_CHAR(ST.TASKSTARTTIME+ST.CYCLETIME,'YYYY-MM-DD HH24:MI:SS'),TO_CHAR(SL.TASKEXESTARTTIME+ST.CYCLETIME,'YYYY-MM-DD HH24:MI:SS'))
                            NEXTEXCUTIME2,st.NEXTEXCUTIME from ScheduledTask st
                            LEFT JOIN factory f ON f.factoryid = st.factoryid
                            left join ScheduledTaskLogs sl on st.ScheduledTaskid=sl.ScheduledTaskid and sl.islatest=1
                            WHERE st.tasktype = {0} and st.isuse=0 and st.status!=3 and not exists (select 1 from ScheduledTaskLogs sl where sl.scheduledtaskid=st.scheduledtaskid and sl.islatest=1 and sl.taskexeendtime is null)";

            DataTable dt = DatabaseHelper.Query_ReturnDatTable(string.Format(strSql, int.Parse(((Enum)taskType).ToString("D"))));
            //筛选出有效需要执行的任务
            var re = dt.AsEnumerable().Where((dr) =>
            {
                if (dr["type"].ToString() == "自动未执行")
                {
                    if (DateTime.Parse(dr["NEXTEXCUTIME"].ToString()) > DateTime.Parse(dr["taskendtime"].ToString())) //下次执行时间大于任务指定结束时间，不执行
                    {
                        return false;
                    }
                    if (DateTime.Parse(dr["NEXTEXCUTIME"].ToString()) > DateTime.Now)//下次执行时间大于当前时间，不执行
                    {
                        return false;
                    }
                }
                return true;
            });
            if (re.Count() > 0)
                return re.CopyToDataTable();
            else
                return dt.Clone();
        }

        /// <summary>
        /// 定时任务类型 （需要增加定时任务的往后添加） add by zhangrj 20240929
        /// </summary>
        public enum TaskTypeEnum
        {
            自动排产 = 1,//除去热表的其他分厂自动排产
            自动开卡 = 2,//除去热表、叶片、工装工具、装配的其他分厂自动开卡
            同步现场台账 = 3,//热表
            预排制造计划_工步 = 4,//热表
            生产准备检查_工步 = 5,//热表
            转工计划接收_工步 = 6,//热表
            滚动制造计划_工步 = 7, //热表
            自动预排产 = 8 //除去热表其他分厂的自动预排产 add by zhangrj 20250113
        }

        /// <summary>
        /// 获取开卡人 add by zhangrj 20240929
        /// </summary>
        /// <param name="factoryID"></param>
        /// <returns></returns>
        public static DataTable GetCreateEmp(string factoryID)
        {
            Dictionary<string, string> dic = new Dictionary<string, string>();
            string sql = string.Format(@"SELECT e.employeeid,e.employeename,e.fullname FROM userattribute u 
                                        INNER JOIN employee e ON e.employeename = u.attributevalue
                                        WHERE u.parentid = '{0}' AND u.userattributename = '开卡人'", factoryID);
            return DatabaseHelper.Query_ReturnDatTable(sql);
        }
    }
}
